﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Web.Http.Controllers;
using System.Net;
using System.Net.Http;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using System.Diagnostics;

using Seven.Member.Web.Model;
using Seven.Web.Http;

namespace Seven.Member.Web.Filters.Http
{
    /// <summary>
    /// 用于验证 ASP.NET WebAPI Controller/Action 访问请求登录状态的过滤器。
    /// 对于标记了 <see cref="AllowAnonymousAttribute"/> 或 <see cref="Seven.Web.AllowAuthorizeAttribute"/> 特性的 Controller/Action，将不会被该过滤器验证。
    /// </summary>
    public class LoginStatusAuthorizeAttribute : HttpAuthorizeAttribute
    {
        /// <summary>
        /// 验证当前请求是否经过有效的登录。
        /// </summary>
        /// <param name="actionContext"></param>
        /// <returns></returns>
        protected override bool IsAuthorized(HttpActionContext actionContext)
        {
            LoginModel model = LoginModelUtility.GetLoginModel(actionContext);
            bool isValid = LoginModelUtility.Validate(model);
            if (SEVENMemberWebConfig.DeveloperModel)
            {
                Debug.WriteLine("Http.LoginStatusAuthorizeAttribute.isValid:{0}", isValid);
                return true;
            }
            return isValid;
        }

        /// <summary>
        /// 当页面请求被判断为 未登录 时，所执行的动作（跳转到登录页面）。
        /// 如果当前请求是 AJAX 请求，则返回一个包含请求错误数据的 JSON 响应。
        /// </summary>
        /// <param name="actionContext"></param>
        protected override void HandleUnauthorizedRequest(HttpActionContext actionContext)
        {
            int statusCode = (int)HttpStatusCode.Unauthorized;
            string statusDescription = "登录超时或未登录，请重新登录！";
            bool friendlyHttpError = SEVENMemberWebConfig.FriendlyHttpError;

            string content = friendlyHttpError ?
                JsonConvert.SerializeObject(new
                {
                    Status = new
                    {
                        result = "Unauthorized",
                        RetCode = statusCode,
                        RetMsg = statusDescription
                    }
                }) :
                JsonConvert.SerializeObject(new
                {
                    result = "Unauthorized",
                    statusCode = statusCode,
                    message = statusDescription
                });

            actionContext.Response = new HttpResponseMessage(friendlyHttpError ? HttpStatusCode.OK : HttpStatusCode.Unauthorized)
            {
                Content = new StringContent(content, Encoding.UTF8, "application/json"),
                ReasonPhrase = System.Web.HttpUtility.HtmlDecode(statusDescription),
                RequestMessage = actionContext.Request,
                Version = actionContext.Request.Version
            };
        }
    }
}
